bitkeeper revision 1.564 (3fa9134cYyjxglAlh2gjmCiQ901Z8g)
authorsmh22@labyrinth.cl.cam.ac.uk <smh22@labyrinth.cl.cam.ac.uk>
Wed, 5 Nov 2003 15:12:12 +0000 (15:12 +0000)
committersmh22@labyrinth.cl.cam.ac.uk <smh22@labyrinth.cl.cam.ac.uk>
Wed, 5 Nov 2003 15:12:12 +0000 (15:12 +0000)
misc vbd tweaks tidies and fixes

tools/internal/dom0_defs.h
tools/internal/xi_phys_grant.c
xen/drivers/block/xen_vbd.c
xen/drivers/ide/ide-xeno.c
xen/drivers/scsi/sd.c
xen/include/hypervisor-ifs/block.h
xen/include/hypervisor-ifs/vbd.h
xen/include/xeno/vbd.h
xenolinux-2.4.22-sparse/arch/xeno/drivers/block/xl_block.c
xenolinux-2.4.22-sparse/arch/xeno/drivers/block/xl_vbd.c

index 40181db15ae7508ef323191885b52cdb9aaffab0..0c0c4080dded27588c2447cfa025f8af2cf8df4c 100644 (file)
@@ -58,11 +58,6 @@ static inline int do_privcmd(unsigned int cmd, unsigned long data)
     return ret;
 }
 
-static inline int do_xen_blkmsg(privcmd_blkmsg_t *blkmsg)
-{
-    return do_privcmd(IOCTL_PRIVCMD_BLKMSG, (unsigned long)blkmsg);
-}
-
 static inline int do_xen_hypercall(privcmd_hypercall_t *hypercall)
 {
     return do_privcmd(IOCTL_PRIVCMD_HYPERCALL, (unsigned long)hypercall);
index 9267c5f85db2f3947fb91282de39bc65e0985d51..c5a608ce6171468317b00aa7b3f3a82b53438266 100644 (file)
@@ -26,12 +26,17 @@ int main(int argc, char *argv[])
     */
     domain  = atoi(argv[2]); 
     device  = atoi(argv[3]); 
-       /* XXX SMH: hack -- generate device name by addition ptn number */
+    /* XXX SMH: hack -- generate device name by addition ptn number */
     vdevice = device + atoi(argv[6]);
     
     op.cmd = BLOCK_IO_OP_VBD_CREATE; 
     op.u.create_info.domain  = domain; 
     op.u.create_info.vdevice = vdevice; 
+    op.u.create_info.mode    = 0; 
+    if ( strchr(argv[1], 'r') )
+       op.u.create_info.mode |= VBD_MODE_R;
+    if ( strchr(argv[1], 'w') )
+        op.u.create_info.mode |= VBD_MODE_W;
 
     ret = do_block_io_op(&op);
 
@@ -49,13 +54,7 @@ int main(int argc, char *argv[])
     op.u.add_info.extent.device       = device; 
     op.u.add_info.extent.start_sector = atol(argv[4]);
     op.u.add_info.extent.nr_sectors   = atol(argv[5]);
-    op.u.add_info.extent.mode         = 0; 
-    if ( strchr(argv[1], 'r') )
-       op.u.add_info.extent.mode |= PHYSDISK_MODE_R;
-    if ( strchr(argv[1], 'w') )
-        op.u.add_info.extent.mode |= PHYSDISK_MODE_W;
 
-    
     ret = do_block_io_op(&op);
 
     if(ret < 0) { 
index dae8e9343a1d13167499b4183e3a1f819022848e..50e8173d88626e6c6d97977c13facd24bac39449 100644 (file)
@@ -45,6 +45,7 @@ long vbd_create(vbd_create_t *create_info)
 
     new_vbd = kmalloc(sizeof(vbd_t), GFP_KERNEL); 
     new_vbd->vdevice = create_info->vdevice; 
+    new_vbd->mode    = create_info->mode; 
     new_vbd->extents = (xen_extent_le_t *)NULL; 
     new_vbd->next    = (vbd_t *)NULL; 
 
@@ -94,7 +95,6 @@ long vbd_add(vbd_add_t *add_info)
     xele->extent.device       = add_info->extent.device; 
     xele->extent.start_sector = add_info->extent.start_sector; 
     xele->extent.nr_sectors   = add_info->extent.nr_sectors; 
-    xele->extent.mode         = add_info->extent.mode; 
     xele->next                = (xen_extent_le_t *)NULL; 
 
     if(!v->extents) {
@@ -141,6 +141,13 @@ int vbd_translate(phys_seg_t * pseg, int *nr_segs,
        return -ENODEV; 
     }
 
+    if(operation == READ && !VBD_CAN_READ(v)) 
+       return -EACCES; 
+    
+    if(operation == WRITE && !VBD_CAN_WRITE(v))
+       return -EACCES; 
+    
+
     /* Now iterate through the list of xen_extents, working out which 
        should be used to perform the translation. */
     sec = pseg->sector_number; 
@@ -151,12 +158,6 @@ int vbd_translate(phys_seg_t * pseg, int *nr_segs,
            /* we've got a match! XXX SMH: should deal with 
               situation where we span multiple xe's */
 
-           if(operation == READ && !(x->extent.mode & PHYSDISK_MODE_R))
-               return -EACCES; 
-
-           if(operation == WRITE && !(x->extent.mode & PHYSDISK_MODE_W))
-               return -EACCES; 
-
            pseg->dev = x->extent.device; 
            pseg->sector_number += x->extent.start_sector; 
 
@@ -189,7 +190,10 @@ void vbd_probe_devices(xen_disk_info_t *xdi, struct task_struct *p)
     for(i = 0; i < VBD_HTAB_SZ; i++) { 
        for(v = p->vbdtab[i]; v; v = v->next) { 
            xdi->disks[xdi->count].device   = v->vdevice; 
-           xdi->disks[xdi->count].type     = XD_TYPE_DISK; // always :-) 
+           xdi->disks[xdi->count].info     = XD_FLAG_VIRT | XD_TYPE_DISK; 
+
+           /* XXX SMH: and now set XD_FLAG_RO if necessary */
+
            xdi->disks[xdi->count].capacity = 0; 
            for(x = v->extents; x; x = x->next) 
                xdi->disks[xdi->count].capacity += x->extent.nr_sectors; 
index 46213fc1c8d752220a9a0f4f6de5aa684adee955..5607164e80cb74d0d74fb350f775e15767495b98 100644 (file)
@@ -55,7 +55,7 @@ void ide_probe_devices(xen_disk_info_t* xdi)
             capacity = current_capacity(drive);
 
             xdi->disks[xdi->count].device   = device; 
-            xdi->disks[xdi->count].type     = type; 
+            xdi->disks[xdi->count].info     = type; 
             xdi->disks[xdi->count].capacity = capacity;
             xdi->count++;
 
index eeb1c5aff20f485458524d32df32d5046a2d944d..81ef215635613a994be039437e00a56898ddaba8 100644 (file)
@@ -1353,7 +1353,7 @@ void scsi_probe_devices(xen_disk_info_t *xdi)
 
        /* XXX SMH: if make generic, need to properly determine 'type' */
         xdi->disks[xdi->count].device   = device;
-       xdi->disks[xdi->count].type     = XD_TYPE_DISK; 
+       xdi->disks[xdi->count].info     = XD_TYPE_DISK; 
         xdi->disks[xdi->count].capacity = capacity; 
         xdi->count++; 
                 
index a5e05a647a231f392f57efbfddb05702de51c074..6d02b4307c5a69ea2bb2c114c03b0da4f21d99f4 100644 (file)
 #define XEN_BLOCK_SPECIAL      4
 #define XEN_BLOCK_PROBE        5   /* get config from hypervisor */
 #define XEN_BLOCK_DEBUG        6   /* debug */
-#define XEN_BLOCK_VBD_CREATE   7   /* create vbd */
-#define XEN_BLOCK_VBD_DELETE   8   /* delete vbd */
-                                   /* XXX SMH: was 'probe vbd' */
-#define XEN_BLOCK_PHYSDEV_GRANT 10 /* grant access to range of disk blocks */
-#define XEN_BLOCK_PHYSDEV_PROBE 11 /* probe for a domain's physdev accesses */
-                                   /* XXX SMH: was 'probe vbd all' */
 
 /* NB. Ring size must be small enough for sizeof(blk_ring_t) <= PAGE_SIZE. */
 #define BLK_RING_SIZE        64
@@ -68,12 +62,10 @@ typedef struct blk_ring_st
 } blk_ring_t;
 
 /*
- *
- * physical disk (xhd) info, used by XEN_BLOCK_PROBE
- *
- */
-
-#define XEN_MAX_DISK_COUNT 100
+ * Information about the real and virtual disks we have; used during 
+ * guest device probing. 
+ */ 
+#define XEN_MAX_DISK_COUNT 64
 
 /* XXX SMH: below types chosen to align with ide_xxx types in ide.h */
 #define XD_TYPE_FLOPPY  0x00
@@ -82,10 +74,19 @@ typedef struct blk_ring_st
 #define XD_TYPE_OPTICAL 0x07
 #define XD_TYPE_DISK    0x20 
 
+#define XD_TYPE_MASK    0x3F
+#define XD_TYPE(_x)     ((_x) & XD_TYPE_MASK) 
+
+/* The top two bits of the type field encode various flags */
+#define XD_FLAG_RO      0x40
+#define XD_FLAG_VIRT    0x80
+#define XD_READONLY(_x) ((_x) & XD_FLAG_RO)
+#define XD_VIRTUAL(_x)  ((_x) & XF_FLAG_VIRT) 
+
 typedef struct xen_disk
 {
-    unsigned short device;       /* device number (see top of file)    */
-    unsigned short type;         /* device type, i.e. disk, cdrom, etc */
+    unsigned short device;       /* device number (opaque 16 bit val)  */
+    unsigned short info;         /* device type and flags              */
     unsigned long  capacity;     /* size in terms of #512 byte sectors */
 } xen_disk_t;
 
index 31c45bf529c759d3ffca5d43b44f550a2307020f..fd50333d7d199b3d0b4680e86952279c8c82f16c 100644 (file)
@@ -2,43 +2,13 @@
 #define __HYP_IFS_VBD_H__
 
 
-#define PHYSDISK_MODE_R 1
-#define PHYSDISK_MODE_W 2
-
-#if 0
-typedef struct xp_disk
-{
-  int mode; /* 0 -> revoke existing access, otherwise bitmask of
-              PHYSDISK_MODE_? constants */
-  int domain;
-  unsigned short device; /* XENDEV_??? + idx */
-  unsigned short partition; /* partition number */
-  unsigned long start_sect;
-  unsigned long n_sectors;
-} xp_disk_t;
-
-#define PHYSDISK_MAX_ACES_PER_REQUEST 254 /* Make it fit in one page */
-typedef struct {
-  int n_aces;
-  int domain;
-  int start_ind;
-  struct {
-    unsigned short device; /* XENDEV_??? + idx */
-    unsigned short partition; /* partition number */
-    unsigned long start_sect;
-    unsigned long n_sectors;
-    unsigned mode;
-  } entries[PHYSDISK_MAX_ACES_PER_REQUEST];
-} physdisk_probebuf_t;
-#endif
-
-
-/* Block I/O trap operations and associated structures.
+/* 
+ * Block I/O trap operations and associated structures.
  */
 
 #define BLOCK_IO_OP_SIGNAL       0    /* let xen know we have work to do */ 
 #define BLOCK_IO_OP_RESET        1    /* reset ring indexes on quiescent i/f */
-#define BLOCK_IO_OP_RING_ADDRESS 2 /* returns machine address of I/O ring */
+#define BLOCK_IO_OP_RING_ADDRESS 2    /* returns machine address of I/O ring */
 #define BLOCK_IO_OP_VBD_CREATE   3    /* create a new VBD for a given domain */
 #define BLOCK_IO_OP_VBD_ADD      4    /* add an extent to a given VBD */
 #define BLOCK_IO_OP_VBD_REMOVE   5    /* remove an extent from a given VBD */
@@ -47,18 +17,26 @@ typedef struct {
 
 typedef struct _xen_extent { 
     u16       device; 
+    u16       unused;                 // pad 
     ulong     start_sector; 
     ulong     nr_sectors;
-    u16       mode; 
 } xen_extent_t; 
 
+
+
+#define VBD_MODE_R         0x1
+#define VBD_MODE_W         0x2
+
+#define VBD_CAN_READ(_v)  ((_v)->mode & VBD_MODE_R)
+#define VBD_CAN_WRITE(_v) ((_v)->mode & VBD_MODE_R)
+
   
 typedef struct _vbd_create { 
     unsigned  domain; 
     u16       vdevice; 
+    u16       mode; 
 } vbd_create_t; 
 
-
 typedef struct _vbd_add { 
     unsigned     domain; 
     u16          vdevice; 
index 8c4d6b099d45ebe90d872b1e854d1cb3abf053e2..7e9d4c3fa059886b28c44fa7a15d19ebc095f7da 100644 (file)
@@ -23,20 +23,20 @@ typedef struct _xen_extent_le {
 */
 typedef struct _vbd { 
     unsigned short    vdevice;   // what the domain refers to this vbd as 
+    unsigned short    mode;      // VBD_MODE_{READONLY,READWRITE}
     xen_extent_le_t  *extents;   // list of xen_extents making up this vbd
     struct _vbd      *next;      // for chaining in the hash table
 } vbd_t; 
 
 #define VBD_HTAB_SZ  16       // no. of entries in the vbd hash table. 
 
-void xen_vbd_initialize(void);
-void xen_refresh_vbd_list (struct task_struct *p);
 long vbd_create(vbd_create_t *create_info); 
 long vbd_add(vbd_add_t *add_info); 
 long vbd_remove(vbd_remove_t *remove_info);
 long vbd_delete(vbd_delete_t *delete_info); 
 
-/* Describes a physical disk extent (part of a block io request) */
+
+/* Describes a [partial] disk extent (part of a block io request) */
 typedef struct {
     unsigned short dev;
     unsigned short nr_sects;
@@ -49,15 +49,4 @@ int vbd_translate(phys_seg_t * pseg, int *nr_segs,
                  struct task_struct *p, int operation); 
 
 
-#if 0
-void destroy_physdisk_aces(struct task_struct *p);
-
-int xen_physdisk_grant(xp_disk_t *);
-int xen_physdisk_probe(struct task_struct *requesting_task,
-                      physdisk_probebuf_t *);
-int xen_physdisk_access_okay(phys_seg_t *pseg, struct task_struct *p,
-                            int operation);
-#endif
-
-
-#endif /* PHYSDISK_ACES__ */
+#endif /* __VBD_H__ */
index 40150a76adbf7262cd655878571a8dd3158163e8..29619bbbc3ea63a1b54913f12416e647399b6779 100644 (file)
@@ -160,6 +160,7 @@ int xenolinux_block_ioctl(struct inode *inode, struct file *filep,
     return 0;
 }
 
+/* check media change: should probably do something here in some cases :-) */
 int xenolinux_block_check(kdev_t dev)
 {
     DPRINTK("xenolinux_block_check\n");
@@ -246,8 +247,6 @@ static int hypervisor_request(unsigned long   id,
 
     switch ( operation )
     {
-//    case XEN_BLOCK_PHYSDEV_GRANT:
-//    case XEN_BLOCK_PHYSDEV_PROBE:
     case XEN_BLOCK_PROBE:
         if ( RING_PLUGGED ) return 1;
        sector_number = 0;
@@ -431,12 +430,6 @@ static void xlblk_response_int(int irq, void *dev_id, struct pt_regs *ptregs)
             }
            break;
            
-        case XEN_BLOCK_VBD_CREATE:
-        case XEN_BLOCK_VBD_DELETE:
-       case XEN_BLOCK_PHYSDEV_GRANT:
-       case XEN_BLOCK_PHYSDEV_PROBE:
-           printk(KERN_ALERT "response for bogus operation %d\n", 
-                  bret->operation); 
         case XEN_BLOCK_PROBE:
             xlblk_control_msg_pending = bret->status;
             break;
index 9656452c43da46c5a6bb18282ad6845f68795f80..7a25020b3934b3e08cd66efe99db19a601a8d043 100644 (file)
@@ -77,7 +77,7 @@ typedef unsigned char bool;
 int __init xlvbd_init(xen_disk_info_t *xdi)
 {
     int i, result, nminors; 
-    struct gendisk *gd;
+    struct gendisk *gd = NULL;
     kdev_t device; 
     unsigned short major, minor, real_minor; 
     bool is_ide, is_scsi; 
@@ -237,6 +237,9 @@ int __init xlvbd_init(xen_disk_info_t *xdi)
            majors[major] = 1; 
        }
 
+       if(XD_READONLY(xdi->disks[i].info)) 
+           set_device_ro(device, 1); 
+
        if(real_minor) { 
 
            /* Need to skankily setup 'partition' information */
@@ -247,29 +250,28 @@ int __init xlvbd_init(xen_disk_info_t *xdi)
        } else { 
        
            /* Some final fix-ups depending on the device type */
-           switch (xdi->disks[i].type
+           switch (XD_TYPE(xdi->disks[i].info)
            { 
+
            case XD_TYPE_CDROM:
-               set_device_ro(device, 1); 
-               
            case XD_TYPE_FLOPPY: 
            case XD_TYPE_TAPE:
                gd->flags[0] = GENHD_FL_REMOVABLE; 
                printk(KERN_ALERT 
                       "Skipping partition check on %s /dev/%s\n", 
-                      xdi->disks[i].type==XD_TYPE_CDROM ? "cdrom" : 
-                      (xdi->disks[i].type==XD_TYPE_TAPE ? "tape" : 
+                      XD_TYPE(xdi->disks[i].info)==XD_TYPE_CDROM ? "cdrom" : 
+                      (XD_TYPE(xdi->disks[i].info)==XD_TYPE_TAPE ? "tape" : 
                        "floppy"), disk_name(gd, MINOR(device), buf)); 
                break; 
-           
+               
            case XD_TYPE_DISK: 
                register_disk(gd, device, gd->nr_real, &xlvbd_block_fops, 
                              xdi->disks[i].capacity);
                break; 
                
            default: 
-               printk(KERN_ALERT "XenoLinux: unknown ide device type %d\n", 
-                      xdi->disks[i].type); 
+               printk(KERN_ALERT "XenoLinux: unknown device type %d\n", 
+                      XD_TYPE(xdi->disks[i].info)); 
                break; 
            }
 
@@ -304,41 +306,36 @@ struct gendisk *xldev_to_gendisk(kdev_t xldev)
 
 void xlvbd_cleanup(void)
 {
-#if 0
-    if ( xlvbd_gendisk == NULL ) return;
-    
-    blk_cleanup_queue(BLK_DEFAULT_QUEUE(XLVIRT_MAJOR));
+    bool is_ide, is_scsi; 
+    struct gendisk *gd; 
+    char *major_name; 
+    int major; 
 
-    xlvbd_gendisk = NULL;
+    for(major = 0; major < XLVBD_MAX_MAJORS; major++) { 
 
-    read_ahead[XLVIRT_MAJOR] = 0;
+       if(!(gd = xlvbd_gendisk[major]))
+           continue; 
 
-    if ( blksize_size[XLVIRT_MAJOR] != NULL )
-    { 
-       kfree(blksize_size[XLVIRT_MAJOR]);
-        blksize_size[XLVIRT_MAJOR] = NULL;
-    }
+       is_ide = IDE_DISK_MAJOR(major);  /* is this an ide device? */
+       is_scsi= SCSI_BLK_MAJOR(major);  /* is this a scsi device? */
+
+       blk_cleanup_queue(BLK_DEFAULT_QUEUE(major)); 
+       
+       if(is_ide) { 
+           major_name = XLIDE_MAJOR_NAME; 
+       } else if(is_scsi) { 
+           major_name = XLSCSI_MAJOR_NAME;
+       } else { 
+           major_name = XLVBD_MAJOR_NAME;
+       }
+
+       if (unregister_blkdev(major, major_name) != 0) 
+           printk(KERN_ALERT "XenoLinux Virtual Block Device Driver:"
+                  "major device %04x uninstalled w/ errors\n", major); 
 
-    if ( hardsect_size[XLVIRT_MAJOR] != NULL )
-    { 
-       kfree(hardsect_size[XLVIRT_MAJOR]);
-        hardsect_size[XLVIRT_MAJOR] = NULL;
-    }
-    
-    if ( max_sectors[XLVIRT_MAJOR] != NULL )
-    { 
-       kfree(max_sectors[XLVIRT_MAJOR]);
-        max_sectors[XLVIRT_MAJOR] = NULL;
-    }
-    
-    if ( unregister_blkdev(XLVIRT_MAJOR, XLVIRT_MAJOR_NAME) != 0 )
-    {
-       printk(KERN_ALERT
-              "XenoLinux Virtual Block Device Driver"
-               " uninstalled w/ errs\n");
     }
-#endif
-    printk(KERN_ALERT "xlvbd_cleanup: not implemented XXX FIXME SMH\n")
+
+    return
 }